home *** CD-ROM | disk | FTP | other *** search
/ The Arsenal Files 8 / The Arsenal Files Collection #8 (Arsenal Computer) (1996).ISO / dosutils / tsbat50.zip / BATRICKS.TXT < prev    next >
Internet Message Format  |  1996-09-01  |  52KB

  1. From ts@uwasa.fi Sun Sep 1 00:00:00 1996
  2. Subject: Batchtricks file information
  3.  
  4. Assorted Batch Tricks                           Sun 1-September-1996
  5. =====================
  6.                                                  All rights reserved
  7.                                Copyright (c) 1993-1996 by Timo Salmi
  8.  
  9. ....................................................................
  10. Prof. Timo Salmi   Co-moderator of news:comp.archives.msdos.announce
  11. Moderating at ftp:// & http://garbo.uwasa.fi archives  193.166.120.5
  12. Department of Accounting and Business Finance  ; University of Vaasa
  13. ts@uwasa.fi http://uwasa.fi/~ts BBS 961-3170972; FIN-65101,  Finland
  14. ....................................................................
  15.  
  16.   ┌───────────────────────────────────────────────────────────┐
  17.   │ This file belongs to TSBAT*.ZIP. Please do not distribute │
  18.   │ this batricks.txt file separately! If you see this file   │
  19.   │ alone on a BBS, please alert the SysOp immediately.       │
  20.   └───────────────────────────────────────────────────────────┘
  21.  
  22. Introduction
  23. ============
  24.  
  25. This file contains assorted batch tricks. The items are in no
  26. particular order. Many, but not all, have been used in the
  27. TSBAT*.ZIP collection of batches. Likewise, there are some useful
  28. further tricks, not documented here, to be found in the TSBAT
  29. batches. Furthermore, many users have sent me useful suggestions and
  30. their own alternative solutions. My best thanks for the material.
  31. You can find much of this feedback and the other users' solutions
  32. stored in the ftp://garbo.uwasa.fi/pc/pd2/tspost*.zip files. For
  33. further batch programming material via the World Wide Web use
  34. http://garbo.uwasa.fi/pc/batchutil.html. Also, connect to my home
  35. page http://uwasa.fi/~ts/ then click my collection of HTTP links and
  36. find the section on programming.
  37.  
  38. You are free to quote brief passages from this BATRICKS.TXT file
  39. provided you clearly indicate the source with a proper
  40. acknowledgment.
  41.  
  42. Comments and corrections are solicited. But if you wish to have
  43. individual batch programming consultation, please rather post your
  44. question to a Usenet newsgroup like news:comp.os.msdos.programmer or
  45. news:alt.msdos.batch. It is much more efficient than asking me by
  46. email. I'd like to help, but I am very pressed for time. I prefer to
  47. pick the questions I answer from the Usenet news. Thus I can answer
  48. publicly at one go if I happen to have an answer. Besides,
  49. newsgroups have a number of readers who might know a better or an
  50. alternative answer. Don't be discouraged, though, if you get a reply
  51. like this from me. I am always glad to hear from fellow batch file
  52. users.
  53. --------------------------------------------------------------------
  54.  
  55. From ts@uwasa.fi Sun Sep 1 00:00:01 1996
  56. Subject: Batch tricks index
  57.  
  58. INDEX
  59. =====
  60.  
  61. 1)  Making "@echo off" MS-DOS version independent
  62. 2)  Deleting all files without being prompted
  63. 3)  Nested for loops in batch files
  64. 4)  Checking whether a directory exists
  65. 5)  Checking that a program is available at the current directory or at path
  66. 6)  Using subroutines and recursion in batches
  67. 7)  Convert a parameter to uppercase
  68. 8)  Appending a new directory to the path
  69. 9)  Comparing two files
  70. 10) Writing an empty line
  71. 11) Customizing the pause message
  72. 12) Complicated renaming of files with for
  73. 13) Checking a file name for wildcards
  74. 14) Preventing breaking the batch
  75. 15) Prevent a break from bypassing your autoexec.bat
  76. 16) Getting the file name extension
  77. 17) The quote character %
  78. 18) Eliminating auxiliary batches
  79. 19) Utilizing the subst command in paths
  80. 20) How to run a batch once a week (testing for the weekday)
  81. 21) Testing if a file name includes a path
  82. 22) Showing the time without enter
  83. 23) Alternatives for testing for the errorlevel value
  84. 24) Redirecting a batch file's output
  85. 25) Testing for environment space sufficiency
  86. 26) A simple trick to "disable" a drive
  87. 27) Sending an escape sequence to the printer
  88. 28) Creating a random string
  89. 29) Finding out the length of a string
  90. 30) How to obtain the MS-DOS version into an environment variable
  91. 31) Finding out the number of regular files on a drive
  92. 32) Augmenting line numbers to a text file
  93. 33) Storing and returning to the original directory (push and pop)
  94. 34) Enticing the current date into an environment variable
  95. 35) Identifying the individual PC
  96. 36) For loop and redirection quirks
  97. 37) Traversing a directory tree
  98. 38) Echoing the redirection symbol
  99. 39) Getting the file basename
  100. 40) A batch to put user input into an environment variable
  101. 41) Getting the last replaceable parameter
  102. 42) Creating an empty file if the file does not already exist
  103. 43) How can I change or remove the disk volume serial number?
  104. 44) How to pause in a batch for a preset number of seconds?
  105. 45) Where can I find a program to compile batches into COMs or EXEs?
  106. 46) How can I test whether a disk is empty or not?
  107. 47) How can I run a different batch depending on the weekday?
  108. --------------------------------------------------------------------
  109.  
  110. From ts@uwasa.fi Sun Sep 1 00:00:02 1996
  111. Subject: Generalizing @echo off
  112.  
  113. 1. Making "@echo off" MS-DOS version independent
  114. ================================================
  115.  
  116. If you want to turn the echo off, and do not wish to show that line
  117. on the screen, you can easily do this by applying
  118.  @echo off
  119.  
  120. There is a catch, however, because this only works since MS-DOS
  121. version 3.30. So if you want to make it general, put the following
  122. line in your autoexec.bat file if you are using MS-DOS 3.30 or
  123. higher
  124.  set _echo=@
  125. Then use the following format in your batches, which will then work
  126. for any MS-DOS version
  127.  %_echo%echo off
  128. --------------------------------------------------------------------
  129.  
  130. From ts@uwasa.fi Sun Sep 1 00:00:03 1996
  131. Subject: Deleting all files
  132.  
  133. 2. Deleting all files without being prompted
  134. ============================================
  135.  
  136. One of the most Frequently Asked Questions (FAQs) about batches is
  137. how to suppress the "Are you sure (Y/N)?" confirmation requirement
  138. for del *.*.  Use the following:
  139.  echo y| del *.*
  140. If you wish to suppress the message too, use
  141.  echo y| del *.* > nul
  142. There is also another alternative for doing this:
  143.  for %f in (*.*) do call del %f
  144. Whether or not it is sensible to suppress the confirmation can be
  145. debated, but these are the tricks anyway.
  146. --------------------------------------------------------------------
  147.  
  148. From ts@uwasa.fi Sun Sep 1 00:00:04 1996
  149. Subject: Nested for loops
  150.  
  151. 3. Nested for loops in batch files
  152. ==================================
  153.  
  154. It is possible to have nested loops of a kind in batch programming.
  155. Consider the following two batches, and try it out by calling
  156. test.bat.
  157.   echo off
  158.   rem TEST.BAT
  159.   for %%f in (a b c d e f) do %comspec% /c test2 %%f
  160.  
  161.   echo off
  162.   rem TEST2.BAT
  163.   for %%g in (1 2 3) do echo %1%%g
  164.  
  165. Alternatively write everything below on a single line
  166.   for %%f in (a b c d e f) do %comspec% /c
  167.     for %%g in (1 2 3) do echo %%f%%g
  168. (The wrap has been used in the text is because of the right margin.
  169. Don't wrap your batch.). The disadvantage of this alternative is
  170. that the echo will be on.
  171. --------------------------------------------------------------------
  172.  
  173. From ts@uwasa.fi Sun Sep 1 00:00:05 1996
  174. Subject: Checking directory existence
  175.  
  176. 4. Checking whether a directory exists
  177. ======================================
  178.  
  179. It is sometimes useful to be able to test whether a particular
  180. directory exists. The following test is true if the %1 directory
  181. does not exist.
  182.  if not exist %1\nul if not exist %1nul echo Directory %1 does not exist
  183.  
  184. Please note that just like many other items, this will not work on
  185. 4DOS or DR-DOS. These otherwise excellent alternatives have many
  186. hidden incompatibilities with vanilla MS-DOS. Furthermore, this does
  187. not seem to work for a CD-ROM. Probably because of the CD-ROM
  188. drivers use a slightly different directory system with no . (dot)
  189. and .. (dot-dot). My thanks to Bjorn Svensson for bringing this to
  190. my attention.
  191. --------------------------------------------------------------------
  192.  
  193. From ts@uwasa.fi Sun Sep 1 00:00:06 1996
  194. Subject: Checking program existence
  195.  
  196. 5. Checking that a program is available at the current directory or at path
  197. ===========================================================================
  198.  
  199. When you call a program from a batch, and do not give the explicit
  200. path to it, it is advisable to test that the program is available
  201. either at the current directory or the default path.
  202.   set _found=
  203.   if exist %1 set _found=yes
  204.   for %%d in (%path%) do if exist %%d\%1 set _found=yes
  205.   for %%d in (%path%) do if exist %%d%1 set _found=yes
  206.   if "%_found%"=="yes" goto _continue
  207.   echo %1 is not at path or the current directory
  208.   goto _out
  209.   :_continue
  210.   echo %1 found at path or in the current directory
  211.   :_out
  212. --------------------------------------------------------------------
  213.  
  214. From ts@uwasa.fi Sun Sep 1 00:00:07 1996
  215. Subject: Subroutines and recursion
  216.  
  217. 6. Using subroutines and recursion in batches
  218. =============================================
  219.  
  220. It is possible to use subroutines within batches. The crucial trick
  221. is setting an environment variable (e.g. _return) to point to a
  222. label where to return after the subroutine has been performed. For
  223. an example see UNPACK.BAT, and BOOT.BAT, the sections :_common and
  224. :_subru.
  225.  
  226. Likewise it is possible to use recursion go emulate subroutines in
  227. batches. (Recursion means that a batch calls itself).
  228. As an example see SAFEDEL.BAT and trace the effects of the line
  229.  for %%f in (%1) do call safedel %%f recurse
  230. Note that safedel could be replaced by %0 because the zeroth
  231. parameter of a batch file points to itself.
  232. --------------------------------------------------------------------
  233.  
  234. From ts@uwasa.fi Sun Sep 1 00:00:08 1996
  235. Subject: Coversion to uppercase
  236.  
  237. 7. Convert a parameter to uppercase
  238. ===================================
  239.  
  240. This example shows how to ensure that the parameter %1 given to the
  241. batch is in uppercase. This utilizes the fact that MS-DOS converts
  242. the path to uppercase. The result is stored in upcase_ and then the
  243. original path is restored.
  244.   set tmp_=%path%
  245.   path=%1
  246.   set upcase_=%path%
  247.   path=%tmp_%
  248.   set tmp_=
  249.  
  250. The also is another method for getting case-independent results.
  251. This is adapted from Jeff Prosise's column in PC Computing, March
  252. 1993, pp. 216-217. If the batch below is called TEST.BAT, it makes
  253. no difference whether you enter "TEST yes" or "TEST YES" or "TEST
  254. yEs".
  255.   @echo off
  256.   if not "%1"=="" set %1=*****
  257.   set status_=
  258.   if "%yes%"=="*****" set status_=yes
  259.   if "%no%"=="*****" set status_=no
  260.   if not "%status_%"=="" echo The parameter %%1 was a %status_%
  261.   if "%status_%"=="" echo The parameter %%1 was neither a yes nor a no
  262.   if not "%1"=="" set %1=
  263. --------------------------------------------------------------------
  264.  
  265. From ts@uwasa.fi Sun Sep 1 00:00:09 1996
  266. Subject: Append new directory to path
  267.  
  268. 8. Appending a new directory to the path
  269. ========================================
  270.  
  271. This often needed trick is basically very simple. For example
  272. to add directory %1 to path use
  273.  path=%path%;%1
  274. Note that you can only use this trick in a batch. It will not work
  275. at the MS-DOS prompt because the environment variables are expanded
  276. (%path%) only within batches.
  277.  
  278. For a full treatment with safeguards against appending non-existing
  279. directories, or appending twice, see ADDPATH.BAT.
  280. --------------------------------------------------------------------
  281.  
  282. From ts@uwasa.fi Sun Sep 1 00:00:10 1996
  283. Subject: Comparing two files
  284.  
  285. 9. Comparing two files
  286. ======================
  287.  
  288. It is possible in batch programming to test whether or not two files
  289. have identical contents. This trick utilizes the external MS-DOS
  290. programs fc.exe and find.exe. (An external MS-DOS program means, of
  291. course, a program that comes with the standard MS-DOS releases. Most
  292. often the MS-DOS external support files are located in a c:\dos
  293. directory.)
  294.   fc %1 %2 > tmp$$$
  295.   type tmp$$$ | find /i "fc: no differences encountered" > diffe$$$
  296.   if exist notsame$ del notsame$
  297.   copy diffe$$$ notsame$ > nul
  298.   if not exist notsame$ echo Files %1 and %2 are different
  299.   if exist notsame$ echo Files %1 and %2 are identical
  300.   if exist tmp$$$ del tmp$$$
  301.   if exist notsame$ del notsame$
  302.   if exist diffe$$$ del diffe$$$
  303. If you think about, this idea can be used for other useful purposes,
  304. too, because it establishes whether a given string is found in a
  305. text file.
  306. --------------------------------------------------------------------
  307.  
  308. From ts@uwasa.fi Sun Sep 1 00:00:11 1996
  309. Subject: Writing an empty line
  310.  
  311. 10. Writing an empty line
  312. =========================
  313.  
  314. This is a simple, but an often needed, useful trick. Just use echo
  315. with (for example) a point (.) after it. As you can see, I have
  316. utilized this batch feature extensively in my batch collection.
  317.  echo.
  318. --------------------------------------------------------------------
  319.  
  320. From ts@uwasa.fi Sun Sep 1 00:00:12 1996
  321. Subject: Customizing the pause message
  322.  
  323. 11. Customizing the pause message
  324. =================================
  325.  
  326. You can easily customize the message given by pause by giving your
  327. own with echo and directing the pause message to nul.
  328. to nul.
  329.  echo Break to quit, any other key to remove the tmp directory
  330.  pause > nul
  331. --------------------------------------------------------------------
  332.  
  333. From ts@uwasa.fi Sun Sep 1 00:00:13 1996
  334. Subject: Complicated renaming with for
  335.  
  336. 12. Complicated renaming of files with for
  337. ==========================================
  338.  
  339. Although this is basically trivial, one does not necessarily come to
  340. think of it. The for statement is quite useful for involved renaming
  341. of files. An example delineates. For example I have the following
  342. files (Turbo Pascal units for TP 4.0, 5.0, 5.5, 6.0 and 7.0). Say
  343. that I wish to rename them to be version 33 instead of 32.
  344.   tspa3340.zip
  345.   tspa3350.zip
  346.   tspa3355.zip
  347.   tspa3360.zip
  348.   tspa3370.zip
  349. The following for-statement does that conveniently.
  350.  for %f in (40 50 55 60 70) do ren tspa32%f.zip tspa33%f.zip
  351. Naturally, renaming is not the only task that can utilize this
  352. trick. I am sure you can readily think of others, like
  353.   for %d in (a b) do format %d:
  354. --------------------------------------------------------------------
  355.  
  356. From ts@uwasa.fi Sun Sep 1 00:00:14 1996
  357. Subject: Checking for wildcards
  358.  
  359. 13. Checking a file name for wildcards
  360. ======================================
  361.  
  362. This example shows how you can test whether a parameter (%1) of a
  363. batch contains wildcards.
  364.   @echo off
  365.   for %%f in (%1) do if "%%f"=="%1" goto _nowilds
  366.   echo Parameter %1 contains wildcards (or is missing)
  367.   :_nowilds
  368. --------------------------------------------------------------------
  369.  
  370. From ts@uwasa.fi Sun Sep 1 00:00:15 1996
  371. Subject: Preventing breaking the batch
  372.  
  373. 14. Preventing breaking the batch
  374. =================================
  375.  
  376. It is possible to prevent the user from interrupting a batch by
  377. using the ctty command to reassign the input (and the output)
  378. device. Here is an example (an elementary password batch requiring
  379. inputting an e). Note the < and > redirections which are needed
  380. while the ctty has been assigned to nul. The ask batch enhancer is
  381. included in the TSBAT collection.
  382.   @echo off
  383.   ctty nul
  384.   echo Now you cannot break the batch with ^C or ^Break > con
  385.   :_ask
  386.   echo Use e to break > con
  387.   ask /b /d < con
  388.   if errorlevel==101 if not errorlevel==102 goto _out
  389.   goto _ask
  390.   :_out
  391.   ctty con
  392.   echo Back to normal. Now you can break the batch with ^C or ^Break.
  393. Note that this trick does not prevent you from rebooting with
  394. alt-crtl-del while the batch is running. For that you need an
  395. external program like noboot.exe from
  396.  86523 Aug 7 1994 ftp://garbo.uwasa.fi/pc/ts/tstsr20.zip
  397.  tstsr20.zip TSR programs (noboot,reslock,sordino,timedown,timeup ...)
  398. (or whichever version number is current).
  399. --------------------------------------------------------------------
  400.  
  401. From ts@uwasa.fi Sun Sep 1 00:00:16 1996
  402. Subject: Forcing autoexec.bat execution
  403.  
  404. 15. Prevent a break from bypassing your autoexec.bat
  405. ====================================================
  406.  
  407. You can actually prevent a quick tapping of the break from bypassing
  408. your autoexec.bat by a variation of the trick in the item above. Put
  409. for example
  410.   shell=c:\command.com /p nul
  411. in your config.sys. Before you do, make sure to have a floppy to
  412. boot from in case something goes wrong. I first saw trick when it
  413. was posted in the Usenet news:comp.os.msdos.programmer newsgroup by
  414. Joseph Gil yogi@cs.ubc.ca.
  415.  
  416. This is not, however, quite all there is to it. You should put
  417.   ctty con
  418. as the last line to your autoexec.bat. If you don't, the keyboard
  419. will not be responding, and you must boot from the floppy you so
  420. sensibly had prepared :-).
  421. --------------------------------------------------------------------
  422.  
  423. From ts@uwasa.fi Sun Sep 1 00:00:17 1996
  424. Subject: Getting the extension
  425.  
  426. 16. Getting the file name extension
  427. ===================================
  428.  
  429. It would be quite useful to be able to extract the extension of a
  430. given file name into an environment variable. Or to be able just to
  431. test whether there is an extension. Here is how to do that. The
  432. batch is based on the information in PC-Magazine July 1992, Vol. 11,
  433. No. 13, page 528. It gives the crucial information that if one
  434. precedes the argument of a for loop with a slash (/), then the
  435. argument is interpreted in two parts. The first part is the first
  436. character of the argument, the second part all the rest. Neat,
  437. indeed.
  438.    The problem with my solution below is that it will not recognize
  439. .* or .??? as extensions. But, of course, one can first test for
  440. wildcards as shown in a previous item "Checking for wildcards". See
  441. e.g. UNPACK.BAT for the utilization of this method.
  442.      @echo off
  443.      set exten_=%1
  444.      :_next
  445.      set prev_=%exten_%
  446.      for %%f in (/%exten_%) do set exten_=%%f
  447.      if ".%exten_%"=="%prev_%" goto _extfound
  448.      if not "%exten_%"=="%prev_%" goto _next
  449.      goto _noext
  450.      :_extfound
  451.      echo The filename %1 has an extension %exten_%
  452.      goto _out
  453.      :_noext
  454.      echo The filename %1 has no extension
  455.      :_out
  456.      set exten_=
  457.      set prev_=
  458. --------------------------------------------------------------------
  459.  
  460. From ts@uwasa.fi Sun Sep 1 00:00:18 1996
  461. Subject: The quote character %
  462.  
  463. 17. The quote character %
  464. =========================
  465.  
  466. As we know %1 indicates the first parameter given to a batch. Thus
  467. for example echo %1 echoes that parameter. But what if you want to
  468. echo the actual string %1 instead. The % character acts as a quote
  469. character. Thus echo %%1 will indeed be a "%1" instead of its usual
  470. interpretation. Try the following simple test
  471.   @echo off
  472.   if "%1"=="" goto _out
  473.   echo %1
  474.   echo %%1
  475.   :_out
  476. See the item on "Eliminating auxiliary batches" for utilizing this
  477. feature. A good example of utilizing this feature is given by
  478. DELPATH.BAT.
  479. --------------------------------------------------------------------
  480.  
  481. From ts@uwasa.fi Sun Sep 1 00:00:19 1996
  482. Subject: Eliminating auxiliary batches
  483.  
  484. 18. Eliminating auxiliary batches
  485. =================================
  486.  
  487. Quite a number of batch programming tasks require an auxiliary batch
  488. which the primary batch has to call. Many of these cases can be
  489. eliminated by making the batch call itself (a kind of recursion).
  490. The auxiliary code is put in the batch itself. The trick is best
  491. illustrated by looking at the SHOW.BAT, which provides a wild-carded
  492. TYPE command, and would normally need an auxiliary file to type each
  493. of the individual files. Another example is given by the SAFEDEL.BAT
  494. batch.
  495.    There is also an another trick for a similar purpose. The primary
  496. batch creates and auxiliary batch or batches, which it then calls.
  497. See DELPATH.BAT for an example of this method. Here is also a simple
  498. demonstration listing the drives on your system. (Only from c to t,
  499. actually because of the wrap I use here).
  500.  @echo off
  501.  echo @echo off> tmp$$$.bat
  502.  echo if exist %%1:\nul echo Drive %%1: is present>> tmp$$$.bat
  503.  for %%d in (c d e f g h i j k l m n o p q r s t) do call tmp$$$ %%d
  504.  del tmp$$$.bat
  505.    There was an inventive twist of this method in PC-Magazine August
  506. 1992, Vol. 11, No. 14, p. 527 for getting the volume label of a
  507. disk. Here is my own example using the same techniques. It sets the
  508. current directory in an environment variable getdir_. I have
  509. utilized this technique in PUSHDIRE.BAT.
  510.   @echo off
  511.   echo @echo off> director.bat
  512.   echo set getdir_=%%2>> director.bat
  513.   echo echo %%getdir_%%>> director.bat
  514.   dir | find "Directory"> go.bat
  515.   call go
  516.   if exist director.bat del director.bat
  517.   if exist go.bat del go.bat
  518. --------------------------------------------------------------------
  519.  
  520. From ts@uwasa.fi Sun Sep 1 00:00:20 1996
  521. Subject: Subst utilization in paths
  522.  
  523. 19. Utilizing the subst command in paths
  524. ========================================
  525.  
  526. I use the following kind of a simple batch to make some of my
  527. directories easy to reach. The way this simple batch is written it
  528. avoids unnecessary errors if the substitution already has been made.
  529. As a last measure it shows the current substitution status.
  530.   @echo off
  531.   if exist m:\nul echo The substitution has already been made
  532.   if not exist m:\nul subst m: c:\math
  533.   if not exist s:\nul subst s: c:\support
  534.   subst
  535. --------------------------------------------------------------------
  536.  
  537. From ts@uwasa.fi Sun Sep 1 00:00:21 1996
  538. Subject: Run a batch one a week
  539.  
  540. 20. How to run a batch once a week (testing for the weekday)
  541. ============================================================
  542.  
  543. The crucial trick is to be able to put the weekday into an
  544. environment variable. For the full treatment see WEEKLY.BAT. The
  545. essential trick needed is below, that is capturing the weekday into
  546. a weekday_ environment variable. No auxiliary programs outside the
  547. normal MS-DOS commands are needed.
  548.   @echo off
  549.   echo.| date | find "Current" > tmp$$$.bat
  550.   echo set weekday_=%%3> current.bat
  551.   call tmp$$$
  552.   echo %weekday_%
  553.   if "%weekday_%"=="Fri" echo Thank God it's Friday
  554.   if exist tmp$$$.bat del tmp$$$.bat
  555.   if exist current.bat del current.bat
  556.   set weekday_=
  557. In fact, if you substitute %%4 for the %%3 in the above, you'll
  558. capture today's date. Neat, eh?
  559. --------------------------------------------------------------------
  560.  
  561. From ts@uwasa.fi Sun Sep 1 00:00:22 1996
  562. Subject: Is path included in file name?
  563.  
  564. 21. Testing if a file name includes a path
  565. ==========================================
  566.  
  567. First of all please see the earlier item "Getting the extension"
  568. because the same ideas are drawn upon. Testing whether the file name
  569. is a bare file name like go.exe or includes a path like
  570. r:\progs\go.exe is quite a complicated task if one wants to allow
  571. wildcarded names like r:\progs\*.exe. This can be done, and here is
  572. how. If one can figure this one out, one can safely say that one has
  573. begun to understand batch files.
  574.   @echo off
  575.   echo @echo off> tmp$$$.bat
  576.   echo set rest_=%%1>> tmp$$$.bat
  577.   echo :_next>> tmp$$$.bat
  578.   echo set prev_=%%rest_%%>> tmp$$$.bat
  579.   echo for %%%%g in (/%%rest_%%) do set rest_=%%%%g>> tmp$$$.bat
  580.   echo if ":%%rest_%%"=="%%prev_%%" goto _found>> tmp$$$.bat
  581.   echo if "\%%rest_%%"=="%%prev_%%" goto _found>> tmp$$$.bat
  582.   echo if not "%%rest_%%"=="%%prev_%%" goto _next>> tmp$$$.bat
  583.   echo goto _nopath>> tmp$$$.bat
  584.   echo :_found>> tmp$$$.bat
  585.   echo set haspath_=yes>> tmp$$$.bat
  586.   echo goto _out>> tmp$$$.bat
  587.   echo :_nopath>> tmp$$$.bat
  588.   echo set haspath_=no>> tmp$$$.bat
  589.   echo :_out>> tmp$$$.bat
  590.   echo set rest_=>> tmp$$$.bat
  591.   echo set prev_=>> tmp$$$.bat
  592.   for %%f in (%1) do call tmp$$$ %%f
  593.   if "%haspath_%"=="yes" echo Filename %1 includes a path
  594.   if "%haspath_%"=="no" echo Filename %1 does not include a path
  595.   rem if exist tmp$$$.bat del tmp$$$.bat
  596.   set haspath_=
  597. --------------------------------------------------------------------
  598.  
  599. From ts@uwasa.fi Sun Sep 1 00:00:23 1996
  600. Subject: Display the time
  601.  
  602. 22. Showing the time without enter
  603. ==================================
  604.  
  605. A simple trick to show the current time:
  606.   echo.| time | find /v "new"
  607. For capturing the time into an environment variable see
  608. LASTBOOT.BAT.
  609. --------------------------------------------------------------------
  610.  
  611. From ts@uwasa.fi Sun Sep 1 00:00:24 1996
  612. Subject: Testing for the errorlevel
  613.  
  614. 23. Alternatives for testing for the errorlevel value
  615. =====================================================
  616.  
  617. Many programs and some MS-DOS commands (like diskcomp, format and
  618. xcopy) return an errorlevel exit code on termination. Testing for
  619. the errorlevel is complicated by the cumulative nature of
  620. errorlevels. Thus if you wish to test if the errorlevel was
  621. (exactly) 2, you must use
  622.  if errorlevel==2 if not errorlevel==3 echo Errorlevel 2
  623. Another alternative is utilizing the for command:
  624.  for %%e in (0 1 2 3 4 5 6 7) do if errorlevel==%%e set _errlev=%%e
  625.  if "%_errlev%"=="2" echo Errorlevel 2
  626. Alternatively, and more generally
  627.  for %%e in (0 1 2 3 4 5 6 7) do if errorlevel==%%e set _errlev=%%e
  628.  if "%_errlev%"=="2" echo Errorlevel %_errlev%
  629. A convenient trick in more complicated batches is using the goto
  630. command:
  631.   for %%e in (0 1 2) do if errorlevel==%%e goto _label%%e
  632.   goto _out
  633.   :_label0
  634.   echo Errorlevel 0
  635.   :_label1
  636.   echo Errorlevel 1
  637.   :_label2
  638.   echo Errorlevel 2
  639.   :_out
  640. See BOOT.BAT for actual usage of this technique.
  641. --------------------------------------------------------------------
  642.  
  643. From ts@uwasa.fi Sun Sep 1 00:00:25 1996
  644. Subject: Redirecting bacth output
  645.  
  646. 24. Redirecting a batch file's output
  647. =====================================
  648.  
  649. Output from within a batch file is easily redirected. Consider a
  650. batchfile example.bat with the following contents
  651.   @echo This is a redirection test> test
  652. Running "example" will produce a file "test" with
  653.   This is a redirection test
  654. The line has an eoln (end of line: ascii 13 + 10) at the end.
  655. Note that it often is advisable not to leave any blank in front of
  656. the > redirection operator.
  657.  
  658. Redirecting the output that a batch produces, is more complicated.
  659. Consider a batchfile example2.bat with the following contents
  660.   @echo This is another redirection test
  661. Running
  662.   example2 > test
  663. will produce an empty "test" file, while the text is echoed on the
  664. standard output. To redirect the output, you need to drive the batch
  665. through the command interpreter command.com like this (provided that
  666. command.com is at path or in the current directory).
  667.   command /c example2 > test
  668. This will redirect the text to the "test" file.
  669.  
  670. There is another quirk of redirection in MS-DOS batch programming
  671. best demonstrated by an example:
  672.   @echo off
  673.   rem This line will create an empty tmp.$$ file > tmp.$$
  674.   :: This line will not create an empty tmp.$$$ file > tmp.$$$
  675.   rem This line will cause problems: Press <ESC>
  676.   :: This line will not cause problems: Press <ESC>
  677. As explained in PC Magazine Vol 12, Number 9, November 9, 1993, the
  678. reason is that the :: is taken as a label and not processed while
  679. the rem basically is an MS-DOS command that will be processed. The
  680. processing will start from the redirection at the end. This is the
  681. the also reason why redirection and the MS-DOS FOR command will
  682. cause problems. (See the entry "For loop and redirection quirks".)
  683. --------------------------------------------------------------------
  684.  
  685. From ts@uwasa.fi Sun Sep 1 00:00:26 1996
  686. Subject: Out of environment space
  687.  
  688. 25. Testing for environment space sufficiency
  689. =============================================
  690.  
  691. If your batch utilizes environment variables there is a possibility
  692. that you run out of environment space. If you get an "Out of
  693. environment space" message the well-known trick to increase your
  694. environment space by using shell configuration in config.sys:
  695.   Example: shell=c:\bin\command.com c:\bin /e:1024 /p
  696.  
  697. A perhaps less-known trick is that you can test in advance if your
  698. batch will run out of environment space. Below is an example showing
  699. you how to test if you have an additional 32 bytes of environment
  700. space still available for your batch:
  701.  @echo off
  702.  set test_=12345678901234567890123456789012
  703.  if "%test_%"=="12345678901234567890123456789012" goto _yes
  704.  echo Insufficient environment space
  705.  goto _out
  706.  :_yes
  707.  echo Sufficient environment space
  708.  set test_=
  709.  rem Whatever you wish to do
  710.  :_out
  711. --------------------------------------------------------------------
  712.  
  713. From ts@uwasa.fi Sun Sep 1 00:00:27 1996
  714. Subject: Disabling a drive
  715.  
  716. 26. A simple trick to "disable" a drive
  717. =======================================
  718.  
  719. It you wish temporarily disable a drive use the subst command for
  720. example as follows
  721.   @echo off
  722.   md c:\none
  723.   subst d: c:\none
  724. To enable it again use
  725.   @echo off
  726.   subst d: /d
  727.   rd c:\none
  728. --------------------------------------------------------------------
  729.  
  730. From ts@uwasa.fi Sun Sep 1 00:00:28 1996
  731. Subject: Escape sequence to printer
  732.  
  733. 27. Sending an escape sequence to the printer
  734. =============================================
  735.  
  736. Here is a truly trivial trick. You cannot send escape sequences to
  737. the printer directory from the command line, but it is quite easy to
  738. do that from a simple batch file:
  739.   @echo ESC%1> prn
  740. where you have to replace the ESC by the true escape character using
  741. your preferred editor. One snag with this methods is that it imposes
  742. a linefeed.
  743. --------------------------------------------------------------------
  744.  
  745. From ts@uwasa.fi Sun Sep 1 00:00:29 1996
  746. Subject: Creating a random string
  747.  
  748. 28. Creating a random string
  749. ============================
  750.  
  751. I was asked on the UseNet news how to create a random string. My
  752. reply. Please study the following example and expand on it
  753.   @echo off
  754.   echo 10 randomize(val(mid$(time$,7,2))) > tmp.bas
  755.   echo 20 open "tmp2.bat" for output as #1 >> tmp.bas
  756.   echo 30 x$ = mid$(str$(int(rnd*10000)),2) >> tmp.bas
  757.   echo 40 print #1,"@set random_=";x$ >> tmp.bas
  758.   echo 50 close #2 >> tmp.bas
  759.   echo 60 system >> tmp.bas
  760.   gwbasic tmp.bas
  761.   call tmp2
  762.   del tmp.bas
  763.   del tmp2.bat
  764.   set
  765. --------------------------------------------------------------------
  766.  
  767. From ts@uwasa.fi Sun Sep 1 00:00:30 1996
  768. Subject: Getting string length
  769.  
  770. 29. Finding out the length of a string
  771. ======================================
  772.  
  773. The task of finding out the length of a string was tackled in PC
  774. Magazine January 26, 1993 issue. The solution is my own and more
  775. general, but naturally it has similar ingredients to the PC
  776. Magazine's.
  777.   @echo off
  778.   set test_=Testing the length of a string
  779.   echo %test_% > len$&$&$
  780.   dir len$&$&$ | find "LEN$&$&$" > go$$$.bat
  781.   echo @echo off> len$&$&$.bat
  782.   echo set length_=%%1>> len$&$&$.bat
  783.   call go$$$
  784.   echo The length is %length_% bytes
  785.   del len$&$&$
  786.   del len$&$&$.bat
  787.   del go$$$.bat
  788. --------------------------------------------------------------------
  789.  
  790. From ts@uwasa.fi Sun Sep 1 00:00:31 1996
  791. Subject: MS-DOS version into environment variable
  792.  
  793. 30. How to obtain the MS-DOS version into an environment variable
  794. =================================================================
  795.  
  796. Here is the code how to do it.
  797.   @echo off
  798.   ver > go$$$.bat
  799.   echo @echo off> ms-dos.bat
  800.   echo set version_=%%2>> ms-dos.bat
  801.   call go$$$
  802.   echo Your MS-DOS version is %version_%
  803.   del go$$$.bat
  804.   del ms-dos.bat
  805.  
  806. MS-DOS 5.0 version introduced many enhancements (like the loadhigh
  807. command, etc) and additions to the command switches (like /B and /S
  808. to the DIR command). Therefore it is useful to be able to test
  809. whether the batch is being run on a system that is at least MS-DOS
  810. 5.0. Below is one option.
  811.   rem Establish whether MS-DOS version 5.0 or later is being used
  812.   set isver50_=
  813.   ver | find "5.0" > tmpfind.$$$
  814.   ver | find "6.0" >> tmpfind.$$$
  815.   ver | find "6.2" >> tmpfind.$$$
  816.   copy tmpfind.$$$ tmpfind1.$$$ > nul
  817.   del tmpfind.$$$
  818.   if exist tmpfind1.$$$ set isver50_=yes
  819.   if exist tmpfind1.$$$ del tmpfind1.$$$
  820. --------------------------------------------------------------------
  821.  
  822. From ts@uwasa.fi Sun Sep 1 00:00:32 1996
  823. Subject: Number of files on a drive
  824.  
  825. 31. Finding out the number of regular files on a drive
  826. ======================================================
  827.  
  828. Try
  829.   attrib /s c:\*.* | find /c "\"
  830. The directories will not be (mis)counted as files as would with the
  831. dir command. Besides the dir command is not recursive until MS-DOS
  832. version 5.0.
  833.   Note that if you do this for the same drive where you reside,
  834. you'll get one too many in the count because of the "|" pipe.
  835. --------------------------------------------------------------------
  836.  
  837. From ts@uwasa.fi Sun Sep 1 00:00:33 1996
  838. Subject: Numbering a file's lines
  839.  
  840. 32. Augmenting line numbers to a text file
  841. ==========================================
  842.  
  843. Occasionally it might be useful to put line number to a text file.
  844. Here is an example how to do it with MS-DOS commands only
  845.   type YourFile.txt | find /v /n "&$&$&$123" > YourNew.txt
  846. The parameter &$&$&$123 stands for an improbable string, since find
  847. /v means displaying all the lines not containing it.
  848. --------------------------------------------------------------------
  849.  
  850. From ts@uwasa.fi Sun Sep 1 00:00:34 1996
  851. Subject: Push and pop a directory
  852.  
  853. 33. Storing and returning to the original directory (push and pop)
  854. =================================================================
  855.  
  856. There are several methods for (non-resident) pushing and popping the
  857. directory by batch file techniques. In other words storing the
  858. current directory, changing the directory in between, and then
  859. returning to the starting directory. PUSHDIRE.BAT and POPDIRE.BAT
  860. give one method where the current drive and directory are stored in
  861. environment variables. The second method, displayed below, is a
  862. direct adaptation from Jeff Prosise's column in PC Computing, March
  863. 1993, pp. 216-217. Later the trick was presented again in Pc
  864. Magazine June 14, 1994, Vol. 13, No. 11, p. 357. The method is a
  865. very clever utilization of the prompt system. An example
  866. illustrates.
  867.   @echo off
  868.   echo @prompt cd $p$_$n:> r:\setback.bat
  869.   %comspec% /c r:\setback> r:\goback.bat
  870.   ::
  871.   rem Change the drive and directory
  872.   c:
  873.   cd \dos
  874.   echo The current directory is
  875.   cd
  876.   rem Do whatever you wish to do there
  877.   pause
  878.   ::
  879.   rem Go back to the original drive and directory
  880.   call r:\goback
  881.   echo Now back in the original directory
  882.   ::
  883.   rem cleanup
  884.   if exist r:\setback.bat del r:\setback.bat
  885.   if exist r:\goback.bat del r:\goback.bat
  886. --------------------------------------------------------------------
  887.  
  888. From ts@uwasa.fi Sun Sep 1 00:00:35 1996
  889. Subject: Date into environment variable
  890.  
  891. 34. Enticing the current date into an environment variable
  892. ==========================================================
  893.  
  894. Like in the item "Storing and returning to the original directory"
  895. there are more than one way of doing this. One method is indicated
  896. in the item "How to run a batch once a week". The other (again)
  897. utilizes the prompt:
  898.   @echo off
  899.   echo @prompt set date_=$d> r:\tmp$$$.bat
  900.   %comspec% /c r:\tmp$$$> r:\tmp2$$$.bat
  901.   call r:\tmp2$$$
  902.   echo %date_%
  903.   del r:\tmp$$$.bat
  904.   del r:\tmp2$$$.bat
  905.  
  906. If you look at your MS-DOS manual for the prompt special $ codes
  907. (like $d) that you can use in the prompt, you'll see that this
  908. method opens quite a number of possibilities of putting information
  909. into environment variables. Exercise: Put the current weekday into
  910. an environment variable. Hint: Apply $d and $h.
  911. --------------------------------------------------------------------
  912.  
  913. From ts@uwasa.fi Sun Sep 1 00:00:36 1996
  914. Subject: Identifying the individual PC
  915.  
  916. 35. Identifying the individual PC
  917. =================================
  918.  
  919. In cases of some batches it is useful to identify the PC the batch
  920. is run on. For example I use several different PCs myself and
  921. occasionally I need to differentiate between them. The solution is
  922. really trivial. Set an environment variable in the autoexec.bat to
  923. designate the PC. I use a variable pcid_ for this purpose. An
  924. outline batch illustrates.
  925.   @echo off
  926.   if "%pcid_%"=="" goto _none
  927.   goto %pcid_%
  928.   :dell
  929.   echo Dell 325N laptop, do whatever
  930.   goto _out
  931.   :trifu
  932.   echo Trifunic 386 desktop, do whatever
  933.   goto _out
  934.   :karvi
  935.   echo "Garfunkel" Pinus 486 desktop, do whatever
  936.   goto _out
  937.   :_none
  938.   echo PC not identified, do whatever
  939.   :_out
  940. For example in the autoexec.bat of my DELL 325N laptop I have
  941.   set pcid_=dell
  942. --------------------------------------------------------------------
  943.  
  944. From ts@uwasa.fi Sun Sep 1 00:00:37 1996
  945. Subject: For loop and redirection
  946.  
  947. 36. For loop and redirection quirks
  948. ===================================
  949.  
  950. A question from the Usenet newsgroups news:comp.os.msdos.misc and
  951. news:comp.os.msdos.programmer:
  952. > I am using DOS 5.0 and I have the following line in my batch file:
  953. > for %%f in (a b c d) do if exist %%f echo put %%f >> tmpfile
  954. > where a,b,c,d are some filenames.
  955. >
  956. > What I expect it to do is to echo the lines
  957. >  put a
  958. >  put b
  959. >  put c
  960. >  put d
  961. > into the file tmpfile.
  962. >
  963. > But what happen is after the "put a" is written to tmpfile, the rest of the
  964. > lines will just echo to the screen, look like that the redirection is not
  965. > working.
  966. >
  967. > If I take away the "if exist" everything is working fine.  I found out
  968. > every time when I use a conditional statement with redirection, it will
  969. > only redirect the first time, the rest will echo to the screen.
  970. >
  971. > Is it the for loop cannot be mixed with the conditional statement and the
  972. > redirection?
  973.  
  974. Yes, it can be mixed, but not so simply in this case. Use the
  975. following batch
  976.   @echo off
  977.   del tmpfile
  978.   for %%f in (a b c d) do if exist %%f call auxil %%f
  979. where auxil.bat contains
  980.   @echo off
  981.   echo put %1>> tmpfile
  982. I'll be darned if I know why :-).
  983.  
  984. In fact it is possible to do this with a single batch by employing
  985. the following method described in an earlier item
  986.   @echo off
  987.   echo @prompt echo put %%%%1$g$g tmpfile> tmp$$$.bat
  988.   %comspec% /c tmp$$$> auxil.bat
  989.   if exist tmpfile del tmpfile
  990.   for %%f in (a b c d) do if exist %%f call auxil %%f
  991.   del tmp$$$.bat
  992.   del auxil.bat
  993. --------------------------------------------------------------------
  994.  
  995. From ts@uwasa.fi Sun Sep 1 00:00:38 1996
  996. Subject: Traversing a directory tree
  997.  
  998. 37. Traversing a directory tree
  999. ===============================
  1000.  
  1001. Traversing it straight up is relatively easy as can be seen from
  1002. this example.
  1003.   @echo off
  1004.   :_loop
  1005.   dir/w
  1006.   if not exist ..\nul goto _out
  1007.   cd ..
  1008.   goto _loop
  1009.   :_out
  1010. Going recursively down through a directory and its subdirectories is
  1011. very complicated. Yet it can be done if you have MS-DOS 5.00 or
  1012. beyond. The SWEEP.BAT batch accompanying tsbat*.zip demonstrates
  1013. how. The method is, however, too difficult to be of real practical
  1014. importance. It is getter to use an auxiliary program for sweeping,
  1015. like ftp://garbo.uwasa.fi/pc/filefind/target15.zip or SWEEP.COM from
  1016. ftp://garbo.uwasa.fi/pc/pcmagvol/vol4n24.zip.
  1017. --------------------------------------------------------------------
  1018.  
  1019. From ts@uwasa.fi Sun Sep 1 00:00:39 1996
  1020. Subject: Echoing the > and >> symbols
  1021.  
  1022. 38. Echoing the redirection symbol
  1023. ==================================
  1024.  
  1025. In certain situations would be useful to be able echo the
  1026. redirection symbol rather than have its perform its redirection
  1027. function. For example your batch file might have a help line like
  1028. this
  1029.   echo The line to customize is "echo dir/w %%%%3\%%2 >> %%new_%%"
  1030. As you see the double quotes pre-empt the redirection. If you left
  1031. them out, the line would result create a file %NEW_% containing
  1032. "The line to customize is echo dir/w %%3\%2".
  1033.    Contrary to Unix, \ cannot be used to cover the special meaning
  1034. of a symbol. As explained in the item "The quote character %" the %
  1035. sign, can as is demonstrated above by the %% pairs. But %> does not
  1036. take precedence over the redirection.
  1037. --------------------------------------------------------------------
  1038.  
  1039. From ts@uwasa.fi Sun Sep 1 00:00:40 1996
  1040. Subject: Getting the file basename
  1041.  
  1042. 39. Getting the file basename
  1043. =============================
  1044.  
  1045. Occasionally one needs to get the file name without the extension.
  1046. Just like getting the extension from a file name using the "for %%f
  1047. in (/%exten_%)" trick, even this can be done with batch commands
  1048. only. The batch code for getting the basename has been presented by
  1049. Neil Rubenking in PC Magazine April 26, 1994, Vol. 13, No. 8, pp.
  1050. 275-276. But enough is enough even with batch tricks. The logic is
  1051. getting overly complicated. One has to draw the line somewhere, stop
  1052. kidding oneself, and start using batch enhancers (external programs
  1053. to help out). I think here the limit has been reached. Hence I have
  1054. included "basename" and "basepath" programs, which you can use to
  1055. create the enhancers. They return the relevant information into an
  1056. environment variable with that name.
  1057.    When you come to think of it. From one viewpoint, what else than
  1058. batch enhancers are all the external MS-DOS commands (usually) in
  1059. your C:\DOS directory?
  1060.    Using basename and basepath is very easy. Below is an example
  1061.        @echo off
  1062.        basename r:\cmand\command.com
  1063.        basepath r:\cmand\command.com
  1064.        echo %basename%
  1065.        echo %basepath%
  1066. You can discard the environment variable simply by applying (note
  1067. the two alternatives):
  1068.        set basename=
  1069.        basepath
  1070. There is also a "basexten" batch enhancer in the /pc/ts/tsbat*.zip
  1071. collection.
  1072.    A batch-only solution is presented below. It owes heavily to a
  1073. posting by Ted Davis tdavis@umr.edu in news:alt.msdos.batch.
  1074.   @echo off
  1075.   ::
  1076.   rem Instructions
  1077.   if "%1"=="" goto _usage
  1078.   ::
  1079.   rem Create an auxiliary directory
  1080.   mkdir tmpaux$$
  1081.   ::
  1082.   rem Create an empty auxiliary file
  1083.   rem > tmpaux$$\%1
  1084.   ::
  1085.   rem Go to the auxiliary directory
  1086.   cd tmpaux$$
  1087.   ::
  1088.   rem Rename the file without extension (this is the trick!)
  1089.   ren %1 *.
  1090.   ::
  1091.   rem Get the new file name into an environment variable
  1092.   for %%f in (*) do set basename=%%f
  1093.   ::
  1094.   rem Let't test it
  1095.   echo The basename is %basename%
  1096.   ::
  1097.   rem Back to the original directory
  1098.   cd ..
  1099.   ::
  1100.   rem Delete the auxiliary file
  1101.   echo.| del tmpaux$$\*
  1102.   ::
  1103.   rem Delete the auxiliary directory
  1104.   rmdir tmpaux$$
  1105.   ::
  1106.   rem Delete the environment variable
  1107.   set basename=
  1108.   ::
  1109.   goto _end
  1110.   ::
  1111.   :_usage
  1112.   echo Usage: %0 [FileNameWithExtension]
  1113.   :_end
  1114. --------------------------------------------------------------------
  1115.  
  1116. From ts@uwasa.fi Sun Sep 1 00:00:41 1996
  1117. Subject: Reading user's input
  1118.  
  1119. 40. A batch to put user input into an environment variable
  1120. ==========================================================
  1121.  
  1122. This definitely must be the neatest batch programming trick I have
  1123. ever seen. It is an adaptation of the batch published in Neil J.
  1124. Rubenking's User-to-User column in PC Magazine June 27, 1995, Vol.
  1125. 14, No. 12, pp. 247-248. It is based on an idea by Tom Lavedas. It
  1126. will remedy the biggest (alleged) flaw in MS-DOS batch programming,
  1127. that is getting user input without any external programs. My
  1128. adaptation puts a simple word input into the INPUT_ environment
  1129. variable. The original inputs a whole sentence, but it is more
  1130. complicated. A single word (or a single letter) input is what is
  1131. usually sufficient in batch programming. The essence of the trick,
  1132. of you want to study it carefully to understand it, is in the fact
  1133. that the time command outputs the word "Enter" which features as an
  1134. auxiliary batch to be run by the SETINPUT.BAT below. An MS-DOS
  1135. version 3.3 or later is required.
  1136.   @echo off
  1137.   rem INPUT.BAT
  1138.   echo This will copy your input to the environment variable INPUT_
  1139.   echo Give your input:
  1140.   fc con nul /lb1 /n | time | find "    1:  "> setinput.bat
  1141.   echo @echo off> enter.bat
  1142.   echo set input_=%%4>> enter.bat
  1143.   call setinput
  1144.   del setinput.bat
  1145.   del enter.bat
  1146.   echo The value of INPUT_=%input_%
  1147. --------------------------------------------------------------------
  1148.  
  1149. From ts@uwasa.fi Sun Sep 1 00:00:42 1996
  1150. Subject: Getting the last input parameter
  1151.  
  1152. 41. Getting the last replaceable parameter
  1153. ==========================================
  1154.  
  1155. As we know, batch files can use the so-called replaceable parameters
  1156. from %0 to %9. It is easy to get the first parameter in a batch
  1157. call. It is %1. (%0 gives the batch name). But what about getting
  1158. the last parameter when you do not know in advance how many
  1159. parameters the call has. Below is the code. It puts the last
  1160. parameter in the environment variable NF_. As an option, it also
  1161. puts the parameters from the first to the last but one into NF1_.
  1162.   @echo off
  1163.   rem INPUT.BAT
  1164.   echo This will copy your input to the environment variable INPUT_
  1165.   echo Give your input:
  1166.   fc con nul /lb1 /n | date | find "    1:  "> setinput.bat
  1167.   echo @echo off> enter.bat
  1168.   echo set input_=%%5>> enter.bat
  1169.   call setinput
  1170.   del setinput.bat
  1171.   del enter.bat
  1172.   echo The value of INPUT_=%input_%
  1173. --------------------------------------------------------------------
  1174.  
  1175. From ts@uwasa.fi Sun Sep 1 00:00:43 1996
  1176. Subject: Creating an empty file
  1177.  
  1178. 42. Creating an empty file if the file does not already exist
  1179. =============================================================
  1180.  
  1181. @echo off
  1182. if exist testfile goto _nocreate
  1183. rem > testfile
  1184. :_nocreate
  1185. --------------------------------------------------------------------
  1186.  
  1187. From ts@uwasa.fi Sun Sep 1 00:00:44 1996
  1188. Subject: Handling disk's serial number
  1189.  
  1190. 43. How can I change or remove the disk volume serial number?
  1191. =============================================================
  1192.  
  1193. Since version 4.0 the disk serial number was added to MS-DOS. When
  1194. you format a disk is it given a number like 4132-1DFF. It is
  1195. possible to change that information with an innovative batch file
  1196. alone. The batch by Bruce W. Shumway can be found in the PC Magazine
  1197. April 23, 1996, Vol. 15 No. 8, pp. 221-222. There also is a program
  1198. SETSER.EXE "Set the disk's serial number" by yours truly in the
  1199. ftp://garbo.uwasa.fi/pc/ts/ts5dos11.zip collection.
  1200. --------------------------------------------------------------------
  1201.  
  1202. From ts@uwasa.fi Sun Sep 1 00:00:45 1996
  1203. Subject: Inserting a delay
  1204.  
  1205. 44. How to pause in a batch for a preset number of seconds?
  1206. ===========================================================
  1207.  
  1208. You can use the MS-DOS CHOICE.COM command for the purpose as the
  1209. example below demonstrates
  1210.   @echo off
  1211.   echo Testing a delay, starting at ...
  1212.   echo.| time | find /v "new"
  1213.   choice /c:. /t:.,5 /n Pausing for five seconds
  1214.   echo ending at ...
  1215.   echo.| time | find /v "new"
  1216. The choice command was introduced with MS-DOS 6. If you have an
  1217. earlier MS-DOS version you can use my similar CHOOSE.EXE from
  1218. ftp://garbo.uwasa.fi/pc/ts/tsutlf15.zip.
  1219. --------------------------------------------------------------------
  1220.  
  1221. From ts@uwasa.fi Sun Sep 1 00:00:46 1996
  1222. Subject: Batch compilers
  1223.  
  1224. 45. Where can I find a program to compile batches into COMs or EXEs?
  1225. ====================================================================
  1226.  
  1227. Since this question is so frequently asked I'll include an answer
  1228. into my batricks.txt information file. From Garbo program archive's
  1229. MS-DOS index file ftp://garbo.uwasa.fi/pc/INDEX.ZIP we can readily
  1230. locate the following files. Personally, I am dubious about batch
  1231. compilers and their complications. In my opinion, if one wants
  1232. distribute executables, it is much better to use a genuine
  1233. programming language like Turbo Pascal or C. I prefer batches in
  1234. their regular source format.
  1235.  
  1236.  37419 Aug 10 1991 ftp://garbo.uwasa.fi/pc/pcmagutl/bat2ex15.zip
  1237.  bat2ex15.zip Compile batch files to be executables, PC-Mag update
  1238.  
  1239.  51299 Oct 31 1994 ftp://garbo.uwasa.fi/pc/batchutil/tbt324.zip
  1240.  tbt324.zip TurboBAT Batch File Compiler, Foley Hi-Tech Systems
  1241. --------------------------------------------------------------------
  1242.  
  1243. From ts@uwasa.fi Sun Sep 1 00:00:47 1996
  1244. Subject: Is a disk empty?
  1245.  
  1246. 46. How can I test whether a disk is empty or not?
  1247. ==================================================
  1248.  
  1249. This question is best answered by an annotated batch source:
  1250.  
  1251.   @echo off
  1252.   rem Provide help if no parameter is given.
  1253.   if "%1"=="" goto _usage
  1254.  
  1255.   rem Check that the input syntax was acceptable.
  1256.   for %%f in (a b A B) do if "%1"=="%%f" goto _label1
  1257.   goto _usage
  1258.  
  1259.   rem See if "bytes free" appears in the directory listing as it will
  1260.   rem if and only if there are files in the directory.
  1261.   :_label1
  1262.   dir %1:\ /s | find "bytes free" > r:\found.$$$
  1263.  
  1264.   rem If "bytes free" was not found r:\found.$$$ file will be empty.
  1265.   rem An empty file will not be copied.
  1266.   copy r:\found.$$$ r:\notempty.$$$ > nul
  1267.  
  1268.   rem If r:\found.$$$ was empty is was not copied, use this fact to test.
  1269.   if exist r:\notempty.$$$ echo Disk %1: is not empty
  1270.   if not exist r:\notempty.$$$ echo Disk %1: is empty
  1271.  
  1272.   rem Delete the auxiliary files.
  1273.   del r:\found.$$$
  1274.   if exist r:\notempty.$$$ del r:\notempty.$$$
  1275.   goto _out
  1276.  
  1277.   :_usage
  1278.   echo Usage: DSKEMPTY [DriveLetter]
  1279.   echo e.g. DSKEMPTY A
  1280.   echo Put no colon (:) after the DriveLetter!
  1281.  
  1282.   :_out
  1283. --------------------------------------------------------------------
  1284.  
  1285. From ts@uwasa.fi Sun Sep 1 00:00:48 1996
  1286. Subject: A different batch each day
  1287.  
  1288. 47. How can I run a different batch depending on the weekday?
  1289. =============================================================
  1290.  
  1291.   @echo off
  1292.   ::
  1293.   rem Let's take care of everything by a single batch file.
  1294.   rem First prepare a batch for each day. For brevity let's prepare
  1295.   rem them for Monday and Tuesday days only.
  1296.   ::
  1297.   echo echo It is Monday today and whatever else you may wish to do>mon.bat
  1298.   echo echo It is Tuesday today and whatever else you may wish to do>tue.bat
  1299.   ::
  1300.   rem The date command produces output like
  1301.   rem Current date is Tue 27/08/1996
  1302.   rem Enter new date (dd-mm-yy):
  1303.   ::
  1304.   rem Utilize this fact by making a batch file tmp$$$.bat which in turn
  1305.   rem runs the batch which is the third parameter (%3) of current.bat
  1306.   rem (Tue.bat in the above).
  1307.   echo.| date | find "Current">tmp$$$.bat
  1308.   echo call %%3>current.bat
  1309.   call tmp$$$.bat
  1310.   ::
  1311.   rem Let's delete the tmp$$$.bat and current.bat files.
  1312.   if exist current.bat del current.bat
  1313.   if exist tmp$$$.bat del tmp$$$.bat
  1314.   ::
  1315.   rem Since this was only a test, let's delete all the daily files, too.
  1316.   if exist mon.bat del mon.bat
  1317.   if exist tue.bat del tue.bat
  1318. --------------------------------------------------------------------
  1319.  
  1320. From ts@uwasa.fi Sun Sep 1 00:02:01 1996
  1321. Subject: Batch programming literature
  1322.  
  1323. Literature
  1324. ==========
  1325.  
  1326. Most books on batch programming, which I have seen, are too
  1327. elementary to be really useful to the readers of this file. Hence
  1328. this list is very brief indeed.
  1329.  
  1330. Jamsa, Kris (1993). Concise Guide to MS-DOS Batch Files. Microsoft
  1331.   Press. (Draws heavily on DEBUG, but might be of general interest
  1332.   to you.)
  1333.  
  1334. Some issues of magazines like the PC Magazine and PC Computing have
  1335. contained much useful MS-DOS lore. But they have gradually become so
  1336. heavily Windows oriented that they are losing their interest and
  1337. usefulness to an MS-DOS user.
  1338.